﻿using Manon.Autofac;
using Manon.ConfigCenter.Web.ApplicationCore.Dtos.Project;
using Manon.ConfigCenter.Web.ApplicationCore.Dtos.ProjectConfig;
using Manon.ConfigCenter.Web.ApplicationCore.Entities;
using Manon.ConfigCenter.Web.ApplicationCore.Interfaces;
using Manon.ConfigCenter.Web.Common;
using Manon.Core.Commons;
using Manon.Core.Extensions;
using Manon.Repository;
using Manon.Repository.Collections;
using Manon.User.Api.ApplicationCore.Entities;
using Microsoft.AspNetCore.Mvc;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Logging;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Linq.Expressions;
using System.Threading.Tasks;

namespace Manon.ConfigCenter.Web.ApplicationCore.Services
{
    public class ProjectService : IProjectService, ISingletonDependency
    {

        /// <summary>
        /// 获取所有项目简要信息列表 无需权限控制
        /// </summary>
        /// <returns></returns>
        public async Task<List<ProjectSimpleOutput>> GetAllProjectSimpleListAsync()
        {
            var logger = Resolver.Resolve<ILogger<EnvironmentService>>();
            try
            {
                List<ProjectSimpleOutput> list = new List<ProjectSimpleOutput>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                var reops = unitOfWork.GetRepository<Projects>();

                var result = await reops.GetAll().OrderBy(n => n.OrderIndex).ThenBy(n => n.Id).ToListAsync();
                if (result == null)
                {
                    return list;
                }

                foreach (var item in result)
                {
                    list.Add(new ProjectSimpleOutput()
                    {
                        Id = item.Id.ToString(),
                        ProjectCode = item.Code,
                        ProjectName = item.ProjectName
                    });
                }
                return list;


            }
            catch (Exception ex)
            {
                logger.LogError("获取环境变量列表异常", ex);
                throw;
            }
        }

        /// <summary>
        /// 获取项目简要信息列表
        /// </summary>
        /// <returns></returns>
        public async Task<List<ProjectSimpleOutput>> GetProjectSimpleListAsync()
        {
            var logger = Resolver.Resolve<ILogger<EnvironmentService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();

                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();

                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);
                List<ProjectSimpleOutput> list = new List<ProjectSimpleOutput>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                var reops = unitOfWork.GetRepository<Projects>();

                var result = await reops.GetAll().OrderBy(n => n.OrderIndex).ThenBy(n => n.Id).ToListAsync();
                if (result == null)
                {
                    return list;
                }

                foreach (var item in result)
                {
                    if (!(listProjectIds.Contains(item.Id) || item.CreateBy == CurrentUserId)) continue;
                    list.Add(new ProjectSimpleOutput()
                    {
                        Id = item.Id.ToString(),
                        ProjectCode = item.Code,
                        ProjectName = item.ProjectName
                    });
                }
                return list;


            }
            catch (Exception ex)
            {
                logger.LogError("获取环境变量列表异常", ex);
                throw;
            }
        }




        public async Task<IPagedList<ProjectsOutput>> GetProjectPageListAsync(GetProjectListInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var roleService = Resolver.Resolve<IRoleService>();
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);

                List<ProjectsOutput> list = new List<ProjectsOutput>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                Expression<Func<Projects, bool>> predicate = n => listProjectIds.Contains(n.Id) || n.CreateBy == CurrentUserId;
                if (!string.IsNullOrEmpty(Input.projectName))
                {
                    predicate = e => e.ProjectName.Contains(Input.projectName);
                }
                if (Input.storageType > 0)
                {
                    predicate = e => e.StorageType == Input.storageType;
                }
                if (Input.Enabled.HasValue)
                {
                    predicate = e => e.Enabled == Input.Enabled.Value;
                }
                var result = await unitOfWork.GetRepository<Projects>().GetPagedListAsync<ProjectsOutput>(predicate, Input);
                return result;
            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }

        public async Task<ProjectsOutput> GetProject(int Id)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();
                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);


                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                var data = await unitOfWork.GetRepository<Projects>().FindAsync(Id);
                if (data == null) return new ProjectsOutput();
                if (!(listProjectIds.Contains(Id) || data.CreateBy == CurrentUserId)) return new ProjectsOutput();

                ProjectsOutput output = new ProjectsOutput();
                output.Id = data.Id;
                output.OrderIndex = data.OrderIndex;
                output.ProjectName = data.ProjectName;
                output.Remark = data.Remark;
                output.Code = data.Code;
                output.Enabled = data.Enabled;
                output.StorageType = data.StorageType;
                output.CreateBy = data.CreateBy;
                output.UpdateBy = data.UpdateBy;
                output.CreateByName = data.CreateByName;
                output.UpdateByName = data.UpdateByName;
                return output;
            }
            catch (Exception ex)
            {
                logger.LogError("获取项目信息异常", ex);
                throw;
            }
        }

        public async Task<Result<ProjectsOutput>> SaveProject(SaveProjectInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var roleService = Resolver.Resolve<IRoleService>();
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                Projects projects = new Projects();
                if (Input.Id > 0)
                {
                    projects = await unitOfWork.GetRepository<Projects>().FindAsync(Input.Id);
                }
                projects.Id = Input.Id;
                projects.Code = Input.Code;
                projects.OrderIndex = Input.OrderIndex;
                projects.ProjectName = Input.ProjectName;
                projects.Remark = Input.Remark;
                projects.UpdateTime = DateTime.Now;
                projects.Enabled = Input.Enabled;
                projects.StorageType = Input.StorageType;

                if (Input.Id == 0)
                {
                    projects.CreateTime = DateTime.Now;
                    projects.CreateBy = identityUser.UserId;
                    projects.CreateByName = identityUser.UserName;
                    projects.UpdateBy = identityUser.UserId;
                    projects.UpdateByName = identityUser.UserName;
                    await unitOfWork.GetRepository<Projects>().InsertAsync(projects);
                }
                else
                {
                    List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);
                    if (!(listProjectIds.Contains(Input.Id) || projects.CreateBy == CurrentUserId)) return Result<ProjectsOutput>.Failed("您没有权限设置启用或者禁用");


                    projects.UpdateBy = identityUser.UserId;
                    projects.UpdateByName = identityUser.UserName;
                    unitOfWork.GetRepository<Projects>().Update(projects);
                }
                await unitOfWork.SaveChangesAsync();
                return Result<ProjectsOutput>.Successed("保存成功!", new ProjectsOutput()
                {
                    Code = projects.Code,
                    CreateTime = projects.CreateTime,
                    Enabled = projects.Enabled,
                    EnabledString = projects.Enabled == true ? "启用" : "禁用",
                    Id = projects.Id,
                    UpdateTime = projects.UpdateTime,
                    OrderIndex = projects.OrderIndex,
                    ProjectName = projects.ProjectName,
                    Remark = projects.Remark,
                    StorageType = projects.StorageType
                });
            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }

        [HttpPost]
        public async Task<Result> SetEnabled(SetEnabledInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();

                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);


                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var project = await unitOfWork.GetRepository<Projects>().FindAsync(Input.Id);
                if (project == null) return null;

                if (!(listProjectIds.Contains(Input.Id) || project.CreateBy == CurrentUserId)) return Result.Failed("您没有权限设置启用或者禁用");


                project.Enabled = Input.Enabled;
                project.UpdateBy = identityUser.UserId;
                project.UpdateByName = identityUser.UserName;
                project.UpdateTime = DateTime.Now;
                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功!");

            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }



        public async Task<Result> SaveProjectSettings(SaveProjectSettingsInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                var repos = unitOfWork.GetRepository<ProjectConfig>();
                var reposProject = unitOfWork.GetRepository<Projects>();
                var reposEnv = unitOfWork.GetRepository<Environments>();
                if (Input.ConfigStatus == 3 || Input.ConfigStatus == 4)
                {
                    return Result.Successed("该状态不能保存提交!");
                }
                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);


                var projectConfig = await repos.GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);

                if (projectConfig != null && projectConfig.CreateBy != CurrentUserId)
                {
                    var project = await reposProject.FindAsync(Input.ProjectId);
                    if (!listProjectIds.Contains(Input.Id)) return Result.Failed("您没有权限设置启用或者禁用");

                    List<int> listEnvIds = await roleService.GetUserEnvIds(CurrentUserId);

                    var env = await reposEnv.FindAsync(Input.EnvId);

                    if (!listEnvIds.Contains(Input.EnvId)) return Result.Failed("您没有权限设置启用或者禁用");

                }

                bool isAdd = false;
                if (projectConfig == null)
                {
                    projectConfig = new ProjectConfig() { CreateTime = DateTime.Now };

                    isAdd = true;
                }
                projectConfig.Id = Input.Id;
                projectConfig.EnvId = Input.EnvId;
                projectConfig.JsonSettings = Input.JsonSettings;
                projectConfig.Path = Input.Path ?? "";
                projectConfig.ProjectId = Input.ProjectId;
                projectConfig.UpdateTime = DateTime.Now;
                projectConfig.VersionNumber = DateTime.Now.ToString("yyMMddHHmmss");
                projectConfig.Remark = Input.Remark;
                projectConfig.ConfigStatus = Input.ConfigStatus;

                projectConfig.UpdateBy = CurrentUserId;
                projectConfig.UpdateByName = identityUser.UserName;
                if (isAdd)
                {
                    projectConfig.CreateBy = CurrentUserId;
                    projectConfig.CreateByName = identityUser.UserName;
                    await repos.InsertAsync(projectConfig);
                }
                else
                {
                    repos.Update(projectConfig);
                }

                await unitOfWork.SaveChangesAsync();
                return Result.Successed("保存成功!");

            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }





        public async Task<ProjectConfigOutput> GetLastConfigSettings(GetLastConfigSettingsInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();



                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var repos = unitOfWork.GetRepository<ProjectConfig>();

                var result = await repos.GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);

                //数据权限
                if (result != null && result.CreateBy != CurrentUserId)
                {
                    List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);

                    if (!listProjectIds.Contains(Input.ProjectId)) return new ProjectConfigOutput();

                    List<int> listEnvIds = await roleService.GetUserEnvIds(CurrentUserId);

                    if (!listEnvIds.Contains(Input.EnvId)) return new ProjectConfigOutput();

                }


                ProjectConfigOutput model = new ProjectConfigOutput();
                if (result != null)
                {
                    model.EnvId = result.EnvId;
                    model.Id = result.Id;
                    model.JsonSettings = result.JsonSettings;
                    model.Path = result.Path;
                    model.ProjectId = result.ProjectId;
                    model.VersionNumber = result.VersionNumber;
                    model.ConfigStatus = result.ConfigStatus;
                    model.Remark = result.Remark;
                }
                return model;

            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }



        public async Task<Result> SetConfigPass(SetConfigPassInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;
                var roleService = Resolver.Resolve<IRoleService>();



                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var repos = unitOfWork.GetRepository<ProjectConfig>();

                var result = await repos.GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);

                if (result == null)
                {
                    return Result.Failed("无此配置");
                }

                //当前用户不是创建人需要判断是否拥有该数据的操作权限
                if (result.CreateBy != CurrentUserId)
                {
                    List<int> listProjectIds = await roleService.GetUserProjectIds(identityUser.UserId);

                    if (!listProjectIds.Contains(Input.ProjectId)) return Result.Failed("您没有权限审批该项目");

                    List<int> listEnvIds = await roleService.GetUserEnvIds(identityUser.UserId);

                    if (!listEnvIds.Contains(Input.EnvId)) return Result.Failed("您没有权限审批该项目");
                }


                result.ConfigStatus = 3;
                result.UpdateBy = identityUser.UserId;
                result.UpdateByName = identityUser.UserName;
                result.UpdateTime = DateTime.Now;
                repos.Update(result);
                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功"); ;

            }
            catch (Exception ex)
            {
                logger.LogError("审核通过异常", ex);
                throw;
            }
        }


        public async Task<Result> SetConfigUnPass(SetConfigUnPassInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();



                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var repos = unitOfWork.GetRepository<ProjectConfig>();

                var result = await repos.GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);

                if (result == null)
                {
                    return Result.Failed("无此配置");
                }

                //当前用户不是创建人需要判断是否拥有该数据的操作权限
                if (result.CreateBy != CurrentUserId)
                {
                    List<int> listProjectIds = await roleService.GetUserProjectIds(identityUser.UserId);

                    if (!listProjectIds.Contains(Input.ProjectId)) return Result.Failed("您没有权限审批该项目");

                    List<int> listEnvIds = await roleService.GetUserEnvIds(identityUser.UserId);

                    if (!listEnvIds.Contains(Input.EnvId)) return Result.Failed("您没有权限审批该项目");
                }


                result.ConfigStatus = 4;
                result.UpdateBy = identityUser.UserId;
                result.UpdateByName = identityUser.UserName;
                result.UpdateTime = DateTime.Now;
                repos.Update(result);
                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功"); ;

            }
            catch (Exception ex)
            {
                logger.LogError("审核不通过异常", ex);
                throw;
            }
        }

        public async Task<Result> PublishConfig(PublishConfigInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var repos = unitOfWork.GetRepository<ProjectConfig>();
                var reposPublish = unitOfWork.GetRepository<ProjectConfigOnline>();
                var reposHistory = unitOfWork.GetRepository<ProjectConfigHistorys>();
                var result = await repos.GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);

                //当前用户不是创建人需要判断是否拥有该数据的操作权限
                if (result != null && result.CreateBy != CurrentUserId)
                {
                    List<int> listProjectIds = await roleService.GetUserProjectIds(identityUser.UserId);

                    if (!listProjectIds.Contains(Input.ProjectId)) return Result.Failed("您没有权限审批该项目");

                    List<int> listEnvIds = await roleService.GetUserEnvIds(identityUser.UserId);

                    if (!listEnvIds.Contains(Input.EnvId)) return Result.Failed("您没有权限审批该项目");
                }


                var publishConfig = await reposPublish.GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);
                if (publishConfig == null)
                {
                    publishConfig = new ProjectConfigOnline();
                    publishConfig.ProjectId = result.ProjectId;
                    publishConfig.EnvId = result.EnvId;
                    publishConfig.JsonSettings = result.JsonSettings;
                    publishConfig.VersionNumber = result.VersionNumber;
                    publishConfig.UpdateTime = DateTime.Now;
                    publishConfig.CreateTime = DateTime.Now;
                    await reposPublish.InsertAsync(publishConfig);
                }
                else
                {
                    publishConfig.JsonSettings = result.JsonSettings;
                    publishConfig.VersionNumber = result.VersionNumber;
                    publishConfig.UpdateTime = DateTime.Now;
                    reposPublish.Update(publishConfig);
                }

                ProjectConfigHistorys history = new ProjectConfigHistorys();
                history.CreateTime = DateTime.Now;
                history.EnvId = result.EnvId;
                history.JsonSettings = result.JsonSettings;
                history.Path = result.Path;
                history.ProjectId = result.ProjectId;
                history.Remark = result.Remark;
                history.UpdateTime = DateTime.Now;
                history.VersionNumber = result.VersionNumber;
                history.CreateBy = CurrentUserId;
                history.CreateByName = identityUser.UserName;
                history.UpdateBy = CurrentUserId;
                history.UpdateByName = identityUser.UserName;
                await reposHistory.InsertAsync(history);


                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功"); ;

            }
            catch (Exception ex)
            {
                logger.LogError("审核不通过异常", ex);
                throw;
            }
        }


        public async Task<Result> FinishConfig(PublishConfigInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var repos = unitOfWork.GetRepository<ProjectConfig>();
                var result = await repos.GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);

                //当前用户不是创建人需要判断是否拥有该数据的操作权限
                if (result != null && result.CreateBy != CurrentUserId)
                {
                    List<int> listProjectIds = await roleService.GetUserProjectIds(identityUser.UserId);

                    if (!listProjectIds.Contains(Input.ProjectId)) return Result.Failed("您没有权限审批该项目");

                    List<int> listEnvIds = await roleService.GetUserEnvIds(identityUser.UserId);

                    if (!listEnvIds.Contains(Input.EnvId)) return Result.Failed("您没有权限审批该项目");
                }

                result.VersionNumber = "";
                result.Remark = "";
                result.UpdateBy = CurrentUserId;
                result.UpdateTime = DateTime.Now;
                result.UpdateByName = identityUser.UserName;
                result.Remark = "";
                result.ConfigStatus = 1;

                repos.Update(result);
                await unitOfWork.SaveChangesAsync();
                return Result.Successed("设置成功"); ;

            }
            catch (Exception ex)
            {
                logger.LogError("审核不通过异常", ex);
                throw;
            }
        }


        /// <summary>
        /// 获取线上已经发布的配置
        /// </summary>
        /// <param name="ProjectId"></param>
        /// <param name="EnvId"></param>
        /// <returns></returns>
        public async Task<string> GetOnlineConfigById(int ProjectId, int EnvId)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();
                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);
                List<int> listEnvIds = await roleService.GetUserEnvIds(identityUser.UserId);
                if (!listProjectIds.Contains(ProjectId)) return "您没有权限审批该项目";
                if (!listEnvIds.Contains(EnvId)) return "您没有权限审批该项目";

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                var result = unitOfWork.FromSql<GetProjectOnlineConfigOutput>($@"select b.JsonSettings from project a
                                join project_config_online b on a.Id=b.ProjectId
                                join environment c on b.EnvId=c.Id
                                where  a.enabled=1 and a.Id={ProjectId} and c.Id={EnvId}  and a.IsDeleted=0 and c.IsDeleted=0 and b.IsDeleted=0  limit 1").FirstOrDefault();
                if (result == null) return string.Empty;

                return result.JsonSettings;
            }
            catch (Exception ex)
            {
                logger.LogError("获取配置异常", ex);
                throw;
            }
        }

        #region
        public async Task<IPagedList<ProjectsConfigHistoryOutput>> GetProjectHistoryPageList(GetProjectHistoryPageListInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();

                List<int> listPermissProjectIds = await roleService.GetUserProjectIds(CurrentUserId);

                List<int> listEnvPermissionIds = await roleService.GetUserEnvIds(CurrentUserId);




                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                Expression<Func<ProjectConfigHistorys, bool>> predicate = n => (listPermissProjectIds.Contains(n.Id) && listEnvPermissionIds.Contains(n.EnvId)) || n.CreateBy == CurrentUserId;
                if (Input.ProjectId > 0)
                {
                    predicate = e => e.ProjectId == Input.ProjectId;
                }
                if (Input.EnvId > 0)
                {
                    predicate = e => e.EnvId == Input.EnvId;
                }
                if (!string.IsNullOrEmpty(Input.VersionNumber))
                {
                    predicate = e => e.VersionNumber.Contains(Input.VersionNumber);
                }
                if (!string.IsNullOrEmpty(Input.Keyword))
                {
                    predicate = e => e.Remark.Contains(Input.Keyword) || e.JsonSettings.Contains(Input.Keyword);
                }
                var result = unitOfWork.GetRepository<ProjectConfigHistorys>().GetPagedList<ProjectsConfigHistoryOutput>(predicate, Input);

                List<int> listProjectIds = result.Items.Select(n => n.ProjectId).ToList();
                List<int> listEnvIds = result.Items.Select(n => n.EnvId).ToList();

                List<Projects> listProjects = await unitOfWork.GetRepository<Projects>().GetAllByWhere(n => listProjectIds.Contains(n.Id)).ToListAsync();

                List<Environments> listEnvs = await unitOfWork.GetRepository<Environments>().GetAllByWhere(n => listEnvIds.Contains(n.Id)).ToListAsync();

                foreach (var item in result.Items)
                {
                    var project = listProjects?.Where(n => n.Id == item.ProjectId).FirstOrDefault();
                    var env = listEnvs?.Where(n => n.Id == item.EnvId).FirstOrDefault();
                    item.ProjectName = project?.ProjectName;
                    item.ProjectCode = project?.Code;
                    item.EnvName = env?.EnvName;
                    item.EnvCode = env?.EnvCode;
                }

                return result;
            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }

        public async Task<ProjectsConfigHistoryOutput> GetProjectHistoryById(int HistoryId)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                var roleService = Resolver.Resolve<IRoleService>();

                List<int> listPermissProjectIds = await roleService.GetUserProjectIds(CurrentUserId);

                List<int> listEnvPermissionIds = await roleService.GetUserEnvIds(CurrentUserId);


                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var result = await unitOfWork.GetRepository<ProjectConfigHistorys>().FindAsync(HistoryId);

                if (result.CreateBy != CurrentUserId)
                {
                    if (!listPermissProjectIds.Contains(result.ProjectId)) return new ProjectsConfigHistoryOutput();
                    if (!listEnvPermissionIds.Contains(result.EnvId)) return new ProjectsConfigHistoryOutput();
                }


                ProjectsConfigHistoryOutput model = new ProjectsConfigHistoryOutput();
                model.CreateTime = result.CreateTime;
                model.EnvId = result.EnvId;
                model.Id = result.Id;
                model.JsonSettings = result.JsonSettings;
                model.Path = result.Path;
                model.ProjectId = result.ProjectId;
                model.Remark = result.Remark;
                model.UpdateTime = result.UpdateTime;
                model.VersionNumber = result.VersionNumber;
                return model;
            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }

        #endregion


        /// <summary>
        /// 获取环境项目密钥生成页
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<IPagedList<GetProjectSecretPageListOutput>> GetProjectSecretPageListAsync(GetProjectSecretPageListInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var roleService = Resolver.Resolve<IRoleService>();
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);
                List<int> listEnvPermissionIds = await roleService.GetUserEnvIds(CurrentUserId);


                List<GetProjectSecretPageListOutput> list = new List<GetProjectSecretPageListOutput>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                Expression<Func<Projects, bool>> predicate = n => listProjectIds.Contains(n.Id) || n.CreateBy == CurrentUserId;
                if (!string.IsNullOrEmpty(Input.projectName))
                {
                    predicate = e => e.ProjectName.Contains(Input.projectName);
                }
                if (Input.Enabled.HasValue)
                {
                    predicate = e => e.Enabled == Input.Enabled.Value;
                }
                var result = await unitOfWork.GetRepository<Projects>().GetPagedListAsync(predicate, Input);

                List<int> listExistProjectIds = result?.Items?.Select(n => n.Id).ToList();
                if (listExistProjectIds == null) listExistProjectIds = new List<int>();

                var secretData = await unitOfWork.GetRepository<ProjectEnvSecret>().GetAllByWhere(n => n.EnvId == Input.EnvId && listExistProjectIds.Contains(n.ProjectId)).ToListAsync();


                foreach (var item in result.Items)
                {
                    GetProjectSecretPageListOutput model = new GetProjectSecretPageListOutput();
                    var secretModel = secretData?.Where(n => n.EnvId == Input.EnvId && n.ProjectId == item.Id).FirstOrDefault();
                    if (secretModel != null)
                    {

                        model.Id = secretModel.Id;
                        model.SecretKey = secretModel.SecretKey;
                        model.ClientId = secretModel.ClientId;
                    }
                    model.Code = item.Code;
                    model.Enabled = item.Enabled;
                    model.EnvId = Input.EnvId;
                    model.OrderIndex = item.OrderIndex;
                    model.ProjectId = item.Id;
                    model.Remark = item.Remark;
                    model.ProjectName = item.ProjectName;
                    list.Add(model);
                }

                PagedList<GetProjectSecretPageListOutput> pageResult = new PagedList<GetProjectSecretPageListOutput>();
                pageResult.IndexFrom = result.IndexFrom;
                pageResult.Items = list;
                pageResult.PageIndex = result.PageIndex;
                pageResult.PageSize = result.PageSize;
                pageResult.TotalCount = result.TotalCount;
                pageResult.TotalPages = result.TotalPages;

                return pageResult;
            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }

        /// <summary>
        /// 生成密钥
        /// </summary>
        /// <param name="Input"></param>
        /// <returns></returns>
        public async Task<Result> CreateEnvProjectSecret(CreateEnvProjectSecretInput Input)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {
                var roleService = Resolver.Resolve<IRoleService>();
                var identityUser = Resolver.Resolve<IIdentityUser>();
                int CurrentUserId = identityUser.UserId;

                List<int> listProjectIds = await roleService.GetUserProjectIds(CurrentUserId);
                List<int> listEnvPermissionIds = await roleService.GetUserEnvIds(CurrentUserId);


                List<GetProjectSecretPageListOutput> list = new List<GetProjectSecretPageListOutput>();

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();

                var project = await unitOfWork.GetRepository<Projects>().GetFirstOrDefaultAsync(n => n.Id == Input.ProjectId && (listProjectIds.Contains(n.Id) || n.CreateBy == CurrentUserId));
                if (project == null || project.CreateBy != CurrentUserId) return Result.Failed("该项目不存在或者无权限操作!");

                var env = await unitOfWork.GetRepository<Environments>().GetFirstOrDefaultAsync(n => n.Id == Input.EnvId && (listEnvPermissionIds.Contains(n.Id) || n.CreateBy == CurrentUserId));
                if (env == null) return Result.Failed("该环境不存在或者无权限操作!");


                var projectEnvSecret = await unitOfWork.GetRepository<ProjectEnvSecret>().GetFirstOrDefaultAsync(n => n.ProjectId == Input.ProjectId && n.EnvId == Input.EnvId);
                if (projectEnvSecret == null)
                {
                    projectEnvSecret = new ProjectEnvSecret();
                    projectEnvSecret.ClientId = project.Code;
                    projectEnvSecret.CreateBy = CurrentUserId;
                    projectEnvSecret.CreateTime = DateTime.Now;
                    projectEnvSecret.EnvId = Input.EnvId;
                    projectEnvSecret.ProjectId = Input.ProjectId;
                    projectEnvSecret.SecretKey = MD5Helper.MD5EncryptShort($"{env.EnvCode}${project.Code}${Guid.NewGuid().ToString()}").ToLower();
                    projectEnvSecret.UpdateBy = CurrentUserId;
                    projectEnvSecret.UpdateTime = DateTime.Now;
                    await unitOfWork.GetRepository<ProjectEnvSecret>().InsertAsync(projectEnvSecret);

                }
                else
                {
                    projectEnvSecret.ClientId = project.Code;
                    projectEnvSecret.EnvId = Input.EnvId;
                    projectEnvSecret.ProjectId = Input.ProjectId;
                    projectEnvSecret.SecretKey = MD5Helper.MD5EncryptShort($"{env.EnvCode}${project.Code}${Guid.NewGuid().ToString()}").ToLower();
                    projectEnvSecret.UpdateBy = CurrentUserId;
                    projectEnvSecret.UpdateTime = DateTime.Now;
                    unitOfWork.GetRepository<ProjectEnvSecret>().Update(projectEnvSecret);
                }
                await unitOfWork.SaveChangesAsync();
                return Result.Successed("生成成功!");
            }
            catch (Exception ex)
            {
                logger.LogError("获取api资源异常", ex);
                throw;
            }
        }


        #region 获取发布的配置 TODO:  需要做管控 
        public Task<GetProjectEnvSecretOutput> GetProjectEnvSecret(string ProjectCode, string EnvCode)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                var param = new List<MySql.Data.MySqlClient.MySqlParameter>();
                param.Add(new MySql.Data.MySqlClient.MySqlParameter("@Code", ProjectCode));
                param.Add(new MySql.Data.MySqlClient.MySqlParameter("@EnvCode", EnvCode));
                var result = unitOfWork.FromSql<GetProjectEnvSecretOutput>($@"select b.ClientId,b.SecretKey from environment a
                    join project_env_secret b on a.id=b.EnvId
                    join project c on b.ProjectId=c.id
                    where a.EnvCode=@EnvCode and c.`Code`=@Code and a.IsDeleted=0 and c.IsDeleted=0 and b.IsDeleted=0 and c.Enabled=1 limit 1 ", param.ToArray()).FirstOrDefault();
                if (result == null) return Task.FromResult<GetProjectEnvSecretOutput>(new GetProjectEnvSecretOutput());

                return Task.FromResult<GetProjectEnvSecretOutput>(result);
            }
            catch (Exception ex)
            {
                logger.LogError("获取配置异常", ex);
                throw;
            }
        }

        public Task<string> GetProjectOnlineConfigById(string ProjectCode, string EnvCode)
        {
            var logger = Resolver.Resolve<ILogger<ProjectService>>();
            try
            {

                var unitOfWork = Resolver.Resolve<IUnitOfWork<ConfigCenterDbContext>>();
                var param = new List<MySql.Data.MySqlClient.MySqlParameter>();
                param.Add(new MySql.Data.MySqlClient.MySqlParameter("@Code", ProjectCode));
                param.Add(new MySql.Data.MySqlClient.MySqlParameter("@EnvCode", EnvCode));
                var result = unitOfWork.FromSql<GetProjectOnlineConfigOutput>($@"select b.JsonSettings from project a
                                join project_config_online b on a.Id=b.ProjectId
                                join environment c on b.EnvId=c.Id
                                where  a.enabled=1 and a.`Code`=@Code and c.EnvCode=@EnvCode  and a.IsDeleted=0 and c.IsDeleted=0 and b.IsDeleted=0  limit 1", param.ToArray()).FirstOrDefault();
                if (result == null) return Task.FromResult<string>(string.Empty);

                return Task.FromResult<string>(result.JsonSettings);
            }
            catch (Exception ex)
            {
                logger.LogError("获取配置异常", ex);
                throw;
            }
        }
        #endregion

    }
}
